package org.candyteam.lgw.runner;

import lombok.SneakyThrows;
import org.candyteam.lgw.annotation.Test;
import org.candyteam.lgw.framework.CommandLineParseResult;
import org.candyteam.lgw.framework.TestResult;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Arrays;


/**
 * 1、从命令行读测试类名，加载测试类
 * 2、扫描@Test注解的测试方法
 */
public class Core {

    public static void main(String[] args) {
        TestResult result = new Core().runMain(args);
        System.out.println(result);
        System.exit(result.wasSuccessful() ? 0 : 1);
    }

    @SneakyThrows
    TestResult runMain(String[] args) {
        TestResult tr = new TestResult();
        CommandLineParseResult commandLineParseResult = CommandLineParseResult.parse(args);
        if (commandLineParseResult.getParseErrors().isEmpty()) {
            commandLineParseResult.getTargetTestClasses().forEach(clazz -> this.execute(clazz, tr));
        } else {
            throw new RuntimeException(commandLineParseResult.getParseErrors().toString());
        }
        return tr;
    }

    private void execute(Class<?> clazz, TestResult tr) {
        Arrays.stream(clazz.getMethods()).forEach(method -> this.invokeTestMethod(method, clazz, tr));
    }

    private void invokeTestMethod(Method method, Class<?> clazz, TestResult tr) {
        if (Arrays.stream(method.getAnnotations()).anyMatch(Test.class::isInstance)) {
            try {
                method.invoke(clazz.newInstance());
            } catch (IllegalAccessException | InstantiationException | InvocationTargetException e) {
                tr.addTestError(e);
            }
            tr.testFinished();
        }
    }
}
